package com.eastfair.auth.service.impl;

import com.alibaba.fastjson.JSON;
import com.baomidou.dynamic.datasource.annotation.DS;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.extension.toolkit.SqlHelper;
import com.eastfair.auth.dao.OrganizationMapper;
import com.eastfair.auth.dto.OrganizationDTO;
import com.eastfair.auth.dto.ResourceOrganizationSaveDTO;
import com.eastfair.auth.entity.*;
import com.eastfair.auth.enumeration.OrganizationOrgTypeEnum;
import com.eastfair.auth.enumeration.ResourceOrganizationResourceTypeEnum;
import com.eastfair.auth.service.*;
import com.eastfair.auth.vo.OrganizationVo;
import com.eastfair.auth.vo.ResourceOrganizationVo;
import com.eastfair.auth.vo.RoleVo;
import com.eastfair.auth.vo.UserOrganizationVo;
import com.eastfair.boot.service.SuperCacheServiceImpl;
import com.eastfair.cache.auth.OrganizationCacheKeyBuilder;
import com.eastfair.cache.auth.PermissionCacheKeyBuilder;
import com.eastfair.cache.repository.CacheOps;
import com.eastfair.constant.BusinessConstant;
import com.eastfair.core.base.R;
import com.eastfair.core.context.ContextUtil;
import com.eastfair.core.model.CacheKey;
import com.eastfair.core.model.CacheKeyBuilder;
import com.eastfair.core.snowflake.DefaultUidGenerator;
import com.eastfair.log.point.PointUtil;
import com.eastfair.projectcore.api.ProjectCoreServiceFeign;
import com.eastfair.core.snowflake.DefaultUidGenerator;
import com.eastfair.projectcore.dto.FunctionDTO;
import com.eastfair.projectcore.dto.MenuDTO;
import com.eastfair.projectcore.vo.FunctionVO;
import com.eastfair.projectcore.vo.MenuVO;
import com.eastfair.util.CodeUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;
import java.util.stream.Collectors;

import static com.eastfair.core.base.R.SUCCESS_CODE;
import static com.eastfair.core.exception.code.ExceptionCode.NODE_NO;

/**
 * <p>
 * 业务实现类
 *
 * </p>
 *
 * @author ligang
 * @date 2021-07-16
 */
@Slf4j
@Service
@Transactional
@DS("#thread.tenant")
public class OrganizationServiceImpl extends SuperCacheServiceImpl<OrganizationMapper, Organization> implements OrganizationService {

    @Autowired
    ProjectCoreServiceFeign projectCoreServiceFeign;

    @Autowired
    UserOrganizationService userOrganizationService;

    @Autowired
    ResourceOrganizationService resourceOrganizationService;

    @Autowired
    RoleService roleService;

    @Autowired
    OrganizationRoleService orgRoleService;

    @Autowired
    MenuRoleService menuRoleService;

    @Autowired
    FunctionRoleService functionRoleService;

    @Autowired
    protected CacheOps cacheOps;

    @Autowired
    private PointUtil pointUtil;

    /**************sharding 分库分表操作 *****************/
    @Override
    public boolean updateByIdOfShard(Organization entity) {
        UpdateWrapper<Organization> updateWrapper = new UpdateWrapper<>();
        //可将指定字段更新为null
        updateWrapper.lambda().eq(Organization::getProjectId, entity.getProjectId()).eq(Organization::getId, entity.getId());
        entity.setProjectId(null);
        //删除缓存
        delCache(entity);
        return SqlHelper.retBool(this.getBaseMapper().update(entity, updateWrapper));
    }


    @Override
    protected CacheKeyBuilder cacheKeyBuilder() {
        return new OrganizationCacheKeyBuilder();
    }

    /**
     * 处理新增相关处理
     *
     * @param model 实体
     * @return 是否成功
     */
    @Override
    protected R<Boolean> handlerSave(Organization model) {
        //雪花ID
        model.setId(DefaultUidGenerator.getUidOfProjectId(model.getProjectId()));
        if (model.getParentId() == null) {
            //组织顶级为1000
            model.setParentId(BusinessConstant.parentId);
        }
        //code 码
        if (StringUtils.isBlank(model.getCode())) {
            model.setCode(queryCode(model));
        }
        if (model.getSequence() == null) {
            //排序
            model.setSequence(1);
            if (model.getParentId() != null) {
                model.setSequence(querySort(model.getParentId()));
            }
        }
        return R.successDef();
    }


    @Override
    public R del(Long id) {
        Organization organization = getById(id);
        if (organization != null) {
            removeResourceUserOfOrg(Arrays.asList(id));
            //同时删除旗下子节点
            delChild(organization);
            organization.setIsDeleted(BusinessConstant.DELETE_YES);
            updateByIdOfShard(organization);
        }
        return R.successDef();
    }

    @Override
    public R delChild(Organization organization) {
        if (organization != null) {
            String code = organization.getCode();
            List<Organization> organizationList = queryAllOfCode(code + ",");
            if (organizationList != null && !organizationList.isEmpty()) {
                for (Organization organization1 : organizationList) {
                    organization1.setIsDeleted(BusinessConstant.DELETE_YES);
                    updateByIdOfShard(organization1);
                }
                //剔除组织关联的资源和用户
                List<Long> orgIds = organizationList.stream().map(Organization::getId).collect(Collectors.toList());
                removeResourceUserOfOrg(orgIds);
            }
        }
        return R.successDef();
    }

    @Override
    public int querySort(Long parentId) {
        if (parentId == 0) {
            return 1;
        }
        List<Organization> organizationList = queryEntityOfParentId(parentId);
        if (organizationList != null && !organizationList.isEmpty()) {
            int max = organizationList.stream().mapToInt(s -> s.getSequence()).max().getAsInt();
            return max + 1;
        }
        return 1;
    }

    @Override
    public String queryCode(Organization model) {
        String code = nonredundantCode();
        if (model.getParentId() != 0) {
            Organization organization = getById(model.getParentId());
            if (organization != null) {
                code = organization.getCode() + "," + code;
            }
        }
        return code;
    }

    /**
     * 获取不重复的code
     *
     * @return
     */
    public String nonredundantCode() {
        String code = CodeUtils.randomCode(6);
        //是否重复
        int num = queryCodeSize(code);
        if (num > 0) {
            nonredundantCode();
        }
        return code;
    }

    @Override
    public void sortTop(Long id) {
        Organization organization = getById(id);
        if (organization.getParentId() == 0) {
            return;
        }
        organization.setSequence(1);
        updateByIdOfShard(organization);
        List<Organization> organizationList = queryEntityOfParentId(organization.getParentId());
        int num = 2;
        if (organizationList != null && !organizationList.isEmpty()) {
            for (Organization organization1 : organizationList) {
                if (!organization1.getId().equals(id)) {
                    organization1.setSequence(num++);
                    updateByIdOfShard(organization1);
                }
            }
        }
    }

    @Override
    public void initSort(Long parentId) {
        List<Organization> organizationList = queryEntityOfParentId(parentId);
        if (organizationList != null && !organizationList.isEmpty()) {
            int num = 1;
            for (Organization organization : organizationList) {
                organization.setSequence(num++);
                updateByIdOfShard(organization);
            }
        }
    }

    @Override
    public List<Organization> queryAllOfCode(String code) {
        QueryWrapper<Organization> queryWrapper = new QueryWrapper<>();
        if (StringUtils.isNotBlank(code)) {
            queryWrapper.lambda().likeRight(Organization::getCode, code);
        }
        queryWrapper.lambda().eq(Organization::getIsDeleted, BusinessConstant.DELETE_NO);
        //排序查询
        queryWrapper.orderByAsc("sequence");
        List<Organization> organizationList = list(queryWrapper);
        return organizationList;
    }

    @Override
    public int queryCodeSize(String code) {
        QueryWrapper<Organization> queryWrapper = new QueryWrapper<>();
        if (StringUtils.isNotBlank(code)) {
            queryWrapper.lambda().eq(Organization::getCode, code);
        }
        queryWrapper.lambda().eq(Organization::getIsDeleted, BusinessConstant.DELETE_NO);
        return count(queryWrapper);
    }

    @Override
    public OrganizationVo loadTree(String parentCode, List<OrganizationVo> organizationVoList) {
        List<OrganizationVo> tree = new ArrayList<>();
        //加载全部角色和菜单
        List<Long> orgIds = organizationVoList.stream().map(OrganizationVo::getId).collect(Collectors.toList());
        Map<Long, List<RoleVo>> roleOfMap = loadRoleOfMap(orgIds);
        Map<Long, List<MenuVO>> menuOrRoleMap = null;
        if (roleOfMap != null) {
            List<RoleVo> roleVoResult = new ArrayList<>();
            for (List<RoleVo> roleVoList : roleOfMap.values()) {
                if (roleVoList != null && !roleVoList.isEmpty()) {
                    roleVoResult.addAll(roleVoList);
                }
            }
            menuOrRoleMap = loadMenuOfMap(roleVoResult);
        }

        //加载组织的角色
        for (OrganizationVo organizationVo : organizationVoList) {
            //加载角色和菜单
            List<RoleVo> roleVoList = roleOfMap.get(organizationVo.getId());
            organizationVo.setRoleVoList(roleVoList);
            List<MenuVO> menuVOList = new ArrayList<>();
            if (roleVoList != null && !roleVoList.isEmpty() && menuOrRoleMap != null) {
                for (RoleVo roleVo : roleVoList) {
                    List<MenuVO> menuVOList1 = menuOrRoleMap.get(roleVo.getId());
                    if (menuVOList1 != null && !menuVOList1.isEmpty()) {
                        menuVOList.addAll(menuVOList1);
                    }
                }
            }
            organizationVo.setMenuVOList(menuVOList);
        }

        for (OrganizationVo organizationVo : organizationVoList) {
            //找到根节点
            if (organizationVo.getCode().equals(parentCode)) {
                tree.add(findChildren(organizationVo, organizationVoList, roleOfMap, menuOrRoleMap));
                break;
            }
        }
        return tree.get(0);
    }

    /**
     * 查找子节点
     *
     * @param organizationVo 根节点
     * @param list
     * @return
     */
    private OrganizationVo findChildren(OrganizationVo organizationVo, List<OrganizationVo> list, Map<Long, List<RoleVo>> roleOfOrgMap, Map<Long, List<MenuVO>> menuOfRoleMap) {
        List<OrganizationVo> children = new ArrayList<>();
        for (OrganizationVo node : list) {
            if (node.getParentId().equals(organizationVo.getId())) {
                //递归调用
                OrganizationVo organizationVo1 = findChildren(node, list, roleOfOrgMap, menuOfRoleMap);
//                //加载角色和菜单
//                List<RoleVo> roleVoList = roleOfOrgMap.get(organizationVo1.getId());
//                organizationVo1.setRoleVoList(roleVoList);
//                List<MenuVO> menuVOList = new ArrayList<>();
//                if (roleVoList != null && !roleVoList.isEmpty() && menuOfRoleMap != null) {
//                    for (RoleVo roleVo : roleVoList) {
//                        List<MenuVO> menuVOList1 = menuOfRoleMap.get(roleVo.getId());
//                        if(menuVOList1!=null && !menuVOList1.isEmpty()){
//                            menuVOList.addAll(menuVOList1);
//                        }
//                    }
//                }
//                organizationVo1.setMenuVOList(menuVOList);
//                //之前代码
////                List<RoleVo> roleVoList = loadRole(Arrays.asList(organizationVo1.getId()));
////                organizationVo1.setRoleVoList(roleVoList);
////                organizationVo1.setMenuVOList(loadMenu(roleVoList));
                children.add(organizationVo1);
            }
        }
        organizationVo.setChildVoList(children);
        return organizationVo;
    }


    @Override
    public R<Organization> createOrg(OrganizationDTO organizationDTO) {
        Organization organization = new Organization();
        organization.setOrgType(organizationDTO.getOrgType());
        organization.setName(organizationDTO.getName());
        if (organizationDTO.getParentId() != null) {
            organization.setParentId(organizationDTO.getParentId());
        }
        organization.setProjectId(organizationDTO.getProjectId());
        save(organization);
        if (organizationDTO.getResourceId() != null) {
            //添加资源
            ResourceOrganizationSaveDTO resourceOrganizationSaveDTO = new ResourceOrganizationSaveDTO();
            resourceOrganizationSaveDTO.setResourceId(organizationDTO.getResourceId());
            resourceOrganizationSaveDTO.setResourceType(organizationDTO.getResourceType());
            resourceOrganizationSaveDTO.setOrganizationId(organization.getId());
            resourceOrganizationSaveDTO.setProjectId(organization.getProjectId());
            resourceOrganizationService.createResource(resourceOrganizationSaveDTO);
        }
        if (organizationDTO.getUserIds() != null && !organizationDTO.getUserIds().isEmpty()) {
            //添加用户信息，如果在组织组上添加用户，说明该用户是管理员
            userOrganizationService.addUserOfOrg(organization.getId(), organizationDTO.getUserIds(), organization.getProjectId());
        }
        //添加角色
        if (organizationDTO.getRoleIds() != null && !organizationDTO.getRoleIds().isEmpty()) {
            addOrgRole(organization.getId(), organizationDTO.getRoleIds(), false);
        }
        return R.success(organization);
    }

    @Override
    public R<Organization> updOrg(OrganizationDTO organizationDTO) {
        List<Organization> organizationList = listOfOrganization(null, Arrays.asList(organizationDTO.getOrgId()));
        if (organizationList != null && !organizationList.isEmpty()) {
            Organization organization = organizationList.get(0);
            organization.setName(organizationDTO.getName());
            updateByIdOfShard(organization);
            if (organizationDTO.getUserIds() != null && !organizationDTO.getUserIds().isEmpty()) {
                //删除用户关联信息
                userOrganizationService.removeUserOfOrg(organization.getId(), organizationDTO.getUserIds());
                //添加用户信息，如果在组织组上添加用户，说明该用户是管理员
                userOrganizationService.addUserOfOrg(organization.getId(), organizationDTO.getUserIds(), organization.getProjectId());
            }
            //添加角色
            if (organizationDTO.getRoleIds() != null && !organizationDTO.getRoleIds().isEmpty()) {
                //更新角色
                updOrgRole(organization.getId(), organizationDTO.getRoleIds(), false);
            }
            return R.success(organization);
        }
        return R.fail("操作失败");
    }

    @Override
    public List<Organization> queryEntityOfParentId(Long parentId) {
        QueryWrapper<Organization> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(Organization::getParentId, parentId);
        queryWrapper.lambda().eq(Organization::getIsDeleted, BusinessConstant.DELETE_NO);
        //排序查询
        queryWrapper.orderByAsc("sequence");
        return list(queryWrapper);
    }

    @Override
    public OrganizationVo findAllById(Long id) {
        Organization organization = getById(id);
        if (organization != null) {
            String code = organization.getCode();
            List<Organization> childOrganizationList = queryAllOfCode(code);
            if (childOrganizationList != null && !childOrganizationList.isEmpty()) {
                List<OrganizationVo> organizationVoList = doToVos(childOrganizationList);
                //将用户和资源加载进去
                loadUserAndResource(organizationVoList);
                OrganizationVo organizationVo = loadTree(code, organizationVoList);

                //将角色加载进去
                List<Long> orgIds = organizationVoList.stream().map(OrganizationVo::getId).collect(Collectors.toList());
                List<RoleVo> roleVoList = loadRole(orgIds);
                organizationVo.setRoleVoList(roleVoList);
                organizationVo.setMenuVOList(loadMenu(roleVoList));
                organizationVo.setFunctionVOList(loadFunction(roleVoList));
                organizationVo.setRoleIds(organizationVo.getRoleVoList() == null ? null : organizationVo.getRoleVoList().stream().map(RoleVo::getId).collect(Collectors.toList()));
                return organizationVo;
            }
        }
        return null;
    }


    @Override
    public OrganizationVo findMenuOrFunctionById(Long orgId) {
        Organization organization = getById(orgId);
        if (organization != null) {
            OrganizationVo organizationVo = new OrganizationVo();
            BeanUtils.copyProperties(organization, organizationVo);
            //将角色加载进去
            List<RoleVo> roleVoList = loadRole(Arrays.asList(orgId));
            organizationVo.setRoleVoList(roleVoList);
            organizationVo.setMenuVOList(loadMenu(roleVoList));
            organizationVo.setRoleIds(organizationVo.getRoleVoList() == null ? null : organizationVo.getRoleVoList().stream().map(RoleVo::getId).collect(Collectors.toList()));
            organizationVo.setFunctionVOList(loadFunction(roleVoList));
            return organizationVo;
        }
        return null;
    }

    @Override
    public List<Long> findOrgOfAdminUser(Long adminUserId) {
        if (adminUserId == null) {
            return null;
        }
        //用户所在的所有节点
        List<UserOrganization> userOrganizationList = userOrganizationService.listOfUserOrganization(null, Arrays.asList(adminUserId), null);
        if (userOrganizationList != null && !userOrganizationList.isEmpty()) {
            List<Long> orgIds = userOrganizationList.stream().map(UserOrganization::getOrganizationId).collect(Collectors.toList());
            //如果包含子节点，说明是父节点，则该节点的人为管理员
            QueryWrapper<Organization> queryWrapper = new QueryWrapper<>();
            queryWrapper.lambda().in(Organization::getParentId, orgIds);
            queryWrapper.lambda().eq(Organization::getIsDeleted, BusinessConstant.DELETE_NO);
            List<Organization> organizationList = list(queryWrapper);
            if (organizationList != null && !organizationList.isEmpty()) {
                List<Long> parentOrgIds = organizationList.stream().map(Organization::getParentId).collect(Collectors.toList());
                return parentOrgIds;
            }

        }
        return null;
    }

    @Override
    public Organization queryOrgOfType(Long projectId, OrganizationOrgTypeEnum type) {
        Organization organization = new Organization();
        organization.setProjectId(projectId);
        organization.setOrgType(type);
        List<Organization> organizationList = listOfOrganization(organization, null);
        if (organizationList != null && !organizationList.isEmpty()) {
            return organizationList.get(0);
        }

        return null;
    }

    @Override
    public List<Organization> queryOrgTypeOfParent(String parentCode, OrganizationOrgTypeEnum type) {
        //查询全部子节点
        List<Organization> childOrganizationList = queryAllOfCode(parentCode);
        if (childOrganizationList != null && !childOrganizationList.isEmpty()) {
            return childOrganizationList.stream().filter(s -> s.getOrgType().equals(type)).collect(Collectors.toList());
        }
        return null;
    }

    @Override
    public List<Organization> queryOrgNameOfParent(String parentCode, String orgName) {
        //查询全部子节点
        List<Organization> childOrganizationList = queryAllOfCode(parentCode);
        if (childOrganizationList != null && !childOrganizationList.isEmpty()) {
            return childOrganizationList.stream().filter(s -> s.getName().equals(orgName)).collect(Collectors.toList());
        }
        return null;
    }

    @Override
    public Organization verifyResourceExistOfOrg(OrganizationDTO organizationDTO) {
        if (organizationDTO.getOrgId() == null || organizationDTO.getResourceId() == null) {
            return null;
        }
        //查询资源
        List<ResourceOrganization> resourceOrganizationList = resourceOrganizationService.findResource(organizationDTO.getResourceId());
        if (resourceOrganizationList == null || resourceOrganizationList.isEmpty()) {
            return null;
        }
        List<Long> resourceOrgIds = resourceOrganizationList.stream().map(ResourceOrganization::getOrganizationId).collect(Collectors.toList());
        //查询节点
        List<Organization> organizationList = listOfOrganization(null, Arrays.asList(organizationDTO.getOrgId()));
        if (organizationList == null || organizationList.isEmpty()) {
            return null;
        }
        Organization organization = organizationList.get(0);
        //是否是该组织
        if (resourceOrgIds.contains(organization.getId())) {
            return organization;
        }
        //没有，则找寻子节点组织
        List<Organization> childOrganizationList = queryAllOfCode(organization.getCode());
        if (childOrganizationList != null && !childOrganizationList.isEmpty()) {
            for (Organization organization1 : childOrganizationList) {
                if (resourceOrgIds.contains(organization1.getId())) {
                    return organization;
                }
            }
        }
        return null;
    }

    @Override
    public List<Long> queryRoleOfResourceId(Long resourceId) {
        //查询资关联的组织id
        List<ResourceOrganization> resourceOrganizationList = resourceOrganizationService.findResource(resourceId);
        if (resourceOrganizationList != null && !resourceOrganizationList.isEmpty()) {
            List<Long> orgIds = resourceOrganizationList.stream().map(ResourceOrganization::getOrganizationId).collect(Collectors.toList());
            //组织关联的角色
            List<OrganizationRole> organizationRoleList = orgRoleService.findOfOrg(orgIds);
            if (organizationRoleList != null && !organizationRoleList.isEmpty()) {
                return organizationRoleList.stream().map(OrganizationRole::getRoleId).collect(Collectors.toList());
            }
        }
        return null;
    }

    @Override
    public List<Long> queryOrgOfResourceId(Long resourceId, Long orgId) {
        Organization organization = getById(orgId);
        if (organization != null) {
            String code = organization.getCode();
            List<Organization> childOrganizationList = queryAllOfCode(code);
            if (childOrganizationList == null || childOrganizationList.isEmpty()) {
                childOrganizationList = new ArrayList<>();
            }
            childOrganizationList.add(organization);
            List<Long> orgIds = childOrganizationList.stream().map(Organization::getId).collect(Collectors.toList());
            ResourceOrganization resourceOrganization = new ResourceOrganization();
            resourceOrganization.setResourceId(resourceId);
            List<ResourceOrganization> resourceOrganizationList = resourceOrganizationService.listOfResourceOrganization(resourceOrganization, orgIds, null);
            if (resourceOrganizationList != null && !resourceOrganizationList.isEmpty()) {
                return resourceOrganizationList.stream().map(ResourceOrganization::getOrganizationId).collect(Collectors.toList());
            }
        }
        return null;
    }

    @Override
    public Map<Long, List<Organization>> queryOrgVoOfResourceId(List<Long> resourceIds, List<Long> orgIds) {
        Map<Long, List<Organization>> result = new HashMap<>();
        for (Long orgId : orgIds) {
            Organization organization = getById(orgId);
            if (organization != null) {
                String code = organization.getCode();
                List<Organization> childOrganizationList = queryAllOfCode(code);
                if (childOrganizationList == null || childOrganizationList.isEmpty()) {
                    childOrganizationList = new ArrayList<>();
                }
                //全部组织
                childOrganizationList.add(organization);
                //查询资源与组织的关联数据
                List<ResourceOrganization> resourceOrganizationList = resourceOrganizationService.listOfResourceOrganization(null, childOrganizationList.stream().map(Organization::getId).collect(Collectors.toList()), resourceIds);
                if (resourceOrganizationList != null && !resourceOrganizationList.isEmpty()) {
                    for (ResourceOrganization resourceOrganization : resourceOrganizationList) {
                        List<Organization> organizationList = new ArrayList<>();
                        for (Organization organization1 : childOrganizationList) {
                            if (resourceOrganization.getOrganizationId() == organization1.getId()) {
                                organizationList.add(organization1);
                            }
                        }
                        result.put(resourceOrganization.getResourceId(), organizationList);
                    }
                }
            }
        }
        return result;
    }

    @Override
    public R addResourceOfOrgIds(Long resourceId, List<Long> orgIds, ResourceOrganizationResourceTypeEnum resourceType) {
        List<ResourceOrganization> resourceOrganizationList = resourceOrganizationService.listOfResourceOrganization(null, orgIds, Arrays.asList(resourceId));
        if (resourceOrganizationList != null && !resourceOrganizationList.isEmpty()) {
            List<Long> orgIds2 = resourceOrganizationList.stream().map(ResourceOrganization::getOrganizationId).collect(Collectors.toList());
            //去除已经存在的组织
            orgIds.removeAll(orgIds2);

        }
        if (orgIds != null && !orgIds.isEmpty()) {
            List<Organization> organizationList = listOfOrganization(null, orgIds);
            if (organizationList != null && !organizationList.isEmpty()) {
                for (Organization organization : organizationList) {
                    //添加资源
                    ResourceOrganizationSaveDTO resourceOrganizationSaveDTO = new ResourceOrganizationSaveDTO();
                    resourceOrganizationSaveDTO.setResourceId(resourceId);
                    resourceOrganizationSaveDTO.setResourceType(resourceType);
                    resourceOrganizationSaveDTO.setOrganizationId(organization.getId());
                    resourceOrganizationSaveDTO.setProjectId(organization.getProjectId());
                    resourceOrganizationService.createResource(resourceOrganizationSaveDTO);
                }
            }
        }
        return R.success();
    }

    @Override
    public R delResource(Long resourceId, Long orgId) {
        Organization organization = getById(orgId);
        if (organization != null) {
            String code = organization.getCode();
            List<Organization> childOrganizationList = queryAllOfCode(code);
            if (childOrganizationList == null || childOrganizationList.isEmpty()) {
                childOrganizationList = new ArrayList<>();
            }
            childOrganizationList.add(organization);
            List<Long> orgIds = childOrganizationList.stream().map(Organization::getId).collect(Collectors.toList());
            List<ResourceOrganization> resourceOrganizationList = resourceOrganizationService.listOfResourceOrganization(null, orgIds, Arrays.asList(resourceId));
            if (resourceOrganizationList != null && !resourceOrganizationList.isEmpty()) {
                for (ResourceOrganization resourceOrganization : resourceOrganizationList) {
                    resourceOrganization.setIsDeleted(BusinessConstant.DELETE_YES);
                    resourceOrganizationService.updateByIdOfShard(resourceOrganization);
                }
            }
        }
        return R.success();
    }


    /**
     * 加载角色信息
     *
     * @param orgIds
     */
    @Override
    public List<RoleVo> loadRole(List<Long> orgIds) {
        if (orgIds == null || orgIds.isEmpty()) {
            return null;
        }
        //批量查询节点的资源和用户信息
        List<OrganizationRole> orgRoleList = orgRoleService.findOfOrg(orgIds);
        if (orgRoleList != null && !orgRoleList.isEmpty()) {
            Set<Long> roleIds = orgRoleList.stream().map(OrganizationRole::getRoleId).collect(Collectors.toSet());
            return roleService.findAllById(new ArrayList<>(roleIds));
        }
        return null;
    }


    public Map<Long, List<RoleVo>> loadRoleOfMap(List<Long> orgIds) {
        if (orgIds == null || orgIds.isEmpty()) {
            return null;
        }
        Map<Long, List<RoleVo>> result = new HashMap<>();
        //批量查询节点的资源和用户信息
        List<OrganizationRole> orgRoleList = orgRoleService.findOfOrg(orgIds);
        if (orgRoleList != null && !orgRoleList.isEmpty()) {
            Set<Long> roleIds = orgRoleList.stream().map(OrganizationRole::getRoleId).collect(Collectors.toSet());
            List<RoleVo> roleVoList = roleService.findAllById(new ArrayList<>(roleIds));
            //组装组织角色信息
            for (Long orgId : orgIds) {
                if (roleVoList == null || roleVoList.isEmpty()) {
                    result.put(orgId, null);
                } else {
                    //过滤角色id
                    List<Long> roleIdList = orgRoleList.stream().filter(s -> s.getOrganizationId().equals(orgId)).map(OrganizationRole::getRoleId).collect(Collectors.toList());
                    //角色id查询角色
                    if (roleIdList != null && !roleIdList.isEmpty()) {
                        result.put(orgId, roleVoList.stream().filter(s -> roleIdList.contains(s.getId())).collect(Collectors.toList()));
                    }
                }
            }
        }
        return result;
    }

    /**
     * 加载菜单信息
     *
     * @param roleVoList
     */
    @Override
    public List<MenuVO> loadMenu(List<RoleVo> roleVoList) {
        if (roleVoList == null || roleVoList.isEmpty()) {
            return null;
        }
        List<MenuRole> menuRoleList = loadMenuRole(roleVoList);
        if (menuRoleList != null && !menuRoleList.isEmpty()) {
            List<Long> menuIds = menuRoleList.stream().map(MenuRole::getMenuId).collect(Collectors.toList());
            MenuDTO menuDTO = new MenuDTO();
            menuDTO.setMenuIds(menuIds);
            R<List<MenuVO>> r = projectCoreServiceFeign.findAllByChildId(menuDTO);
            if (r.getCode() == SUCCESS_CODE) {
                return r.getData();
            }
        }
        return null;
    }


    /**
     * 加载菜单的权限标识信息
     *
     * @param roleVoList
     */
    @Override
    public List<String> loadMenuPermission(List<RoleVo> roleVoList) {
        if (roleVoList == null || roleVoList.isEmpty()) {
            return null;
        }
        List<MenuRole> menuRoleList = loadMenuRole(roleVoList);
        if (menuRoleList != null && !menuRoleList.isEmpty()) {
            List<Long> menuIds = menuRoleList.stream().map(MenuRole::getMenuId).collect(Collectors.toList());
            MenuDTO menuDTO = new MenuDTO();
            menuDTO.setMenuIds(menuIds);
            R<List<String>> r = projectCoreServiceFeign.findPermissionAllByChildId(menuDTO);
            if (r.getCode() == SUCCESS_CODE) {
                return r.getData();
            }
        }
        return null;
    }


    public Map<Long, List<MenuVO>> loadMenuOfMap(List<RoleVo> roleVoList) {
        if (roleVoList == null || roleVoList.isEmpty()) {
            return null;
        }
        Map<Long, List<MenuVO>> result = new HashMap<>();
        List<MenuRole> menuRoleList = loadMenuRole(roleVoList);
        if (menuRoleList != null && !menuRoleList.isEmpty()) {
            List<Long> menuIds = menuRoleList.stream().map(MenuRole::getMenuId).collect(Collectors.toList());
            MenuDTO menuDTO = new MenuDTO();
            menuDTO.setMenuIds(menuIds);
            R<List<MenuVO>> r = projectCoreServiceFeign.findAllByChildId(menuDTO);
            if (r.getCode() == SUCCESS_CODE) {
                List<MenuVO> menuVOList = r.getData();
                //组装角色菜单信息
                for (RoleVo roleVo : roleVoList) {
                    if (menuVOList == null || menuVOList.isEmpty()) {
                        result.put(roleVo.getId(), null);
                    } else {
                        //过滤菜单id
                        List<Long> menuIdList = menuRoleList.stream().filter(s -> s.getRoleId().equals(roleVo.getId())).map(MenuRole::getMenuId).collect(Collectors.toList());
                        //菜单id查询菜单
                        if (menuIdList != null && !menuIdList.isEmpty()) {
                            result.put(roleVo.getId(), menuVOList.stream().filter(s -> menuIdList.contains(s.getId())).collect(Collectors.toList()));
                        }
                    }
                }
            }
        }
        return result;
    }


    @Override
    public List<MenuRole> loadMenuRole(List<RoleVo> roleVoList) {
        if (roleVoList == null || roleVoList.isEmpty()) {
            return null;
        }
        List<Long> roleIds = roleVoList.stream().map(RoleVo::getId).collect(Collectors.toList());
        List<MenuRole> menuRoleList = menuRoleService.list(null, null, roleIds);
        return menuRoleList;
    }


    /**
     * 加载事件信息
     *
     * @param roleVoList
     */
    @Override
    public List<FunctionVO> loadFunction(List<RoleVo> roleVoList) {
        if (roleVoList == null || roleVoList.isEmpty()) {
            return null;
        }
        List<FunctionRole> functionRoleList = loadFunctionRole(roleVoList);
        if (functionRoleList != null && !functionRoleList.isEmpty()) {
            List<Long> functionIds = functionRoleList.stream().map(FunctionRole::getFunctionId).collect(Collectors.toList());
            FunctionDTO functionDTO = new FunctionDTO();
            functionDTO.setFunctionIds(functionIds);
            R<List<FunctionVO>> r = projectCoreServiceFeign.findFunctionAll(functionDTO);
            if (r.getCode() == SUCCESS_CODE) {
                return r.getData();
            }
        }
        return null;
    }

    @Override
    public List<FunctionRole> loadFunctionRole(List<RoleVo> roleVoList) {
        if (roleVoList == null || roleVoList.isEmpty()) {
            return null;
        }
        List<Long> roleIds = roleVoList.stream().map(RoleVo::getId).collect(Collectors.toList());
        return functionRoleService.list(null, null, roleIds);
    }


    @Override
    public R removeResourceUserOfOrg(List<Long> orgIds) {
        //删除关联的资源
        resourceOrganizationService.delOfOrgIds(orgIds);
        userOrganizationService.delOfOrgIds(orgIds);
        return R.success();
    }

    public void loadUserAndResource(List<OrganizationVo> organizationVoList) {
        if (organizationVoList != null && !organizationVoList.isEmpty()) {
            //抓取所有节点idz
            List<Long> orgIds = organizationVoList.stream().map(OrganizationVo::getId).collect(Collectors.toList());
            //批量查询节点的资源和用户信息
            List<ResourceOrganizationVo> resourceOrganizationList = resourceOrganizationService.queryResource(orgIds);
            List<UserOrganizationVo> userOrganizationVoList = userOrganizationService.queryUserVoByOrg(orgIds);
            //将用户和资源加载进去
            for (OrganizationVo organizationVo : organizationVoList) {
                //定义list
                List<ResourceOrganizationVo> resourceOrganizationVos = new ArrayList<>();
                List<UserOrganizationVo> userOrganizationVoList1 = new ArrayList<>();

                if (resourceOrganizationList != null && !resourceOrganizationList.isEmpty()) {
                    for (ResourceOrganizationVo resourceOrganizationVo : resourceOrganizationList) {
                        if (organizationVo.getId().equals(resourceOrganizationVo.getOrganizationId())) {
                            resourceOrganizationVos.add(resourceOrganizationVo);
                        }
                    }
                }
                if (userOrganizationVoList != null && !userOrganizationVoList.isEmpty()) {
                    for (UserOrganizationVo userOrganizationVo : userOrganizationVoList) {
                        if (organizationVo.getId().equals(userOrganizationVo.getOrganizationId())) {
                            userOrganizationVoList1.add(userOrganizationVo);
                        }
                    }
                }
                if (resourceOrganizationVos != null && !resourceOrganizationVos.isEmpty()) {
                    organizationVo.setResourceOrganizationVo(resourceOrganizationVos);
                }
                if (userOrganizationVoList1 != null && !userOrganizationVoList1.isEmpty()) {
                    organizationVo.setUserOrganizationVoList(userOrganizationVoList1);
                }
            }
        }
    }


    @Override
    public List<Organization> listOfOrganization(Organization organization, List<Long> ids) {
        //查询
        QueryWrapper<Organization> queryWrapper = new QueryWrapper<>();
        if (organization != null) {
            if (organization.getParentId() != null) {
                queryWrapper.lambda().eq(Organization::getParentId, organization.getParentId());
            }
            if (organization.getId() != null) {
                queryWrapper.lambda().eq(Organization::getId, organization.getId());
            }
            if (StringUtils.isNotBlank(organization.getCode())) {
                queryWrapper.lambda().eq(Organization::getCode, organization.getCode());
            }
            if (organization.getOrgType() != null) {
                queryWrapper.lambda().eq(Organization::getOrgType, organization.getOrgType().getCode());
            }
            if (organization.getName() != null) {
                queryWrapper.lambda().eq(Organization::getName, organization.getName());
            }
        }

        if (organization != null && organization.getProjectId() != null) {
            queryWrapper.lambda().eq(Organization::getProjectId, organization.getProjectId());
        } else if (ContextUtil.getProjectId() != null) {
            queryWrapper.lambda().eq(Organization::getProjectId, ContextUtil.getProjectId());
        }


        if (ids != null && !ids.isEmpty()) {
            queryWrapper.lambda().in(Organization::getId, ids);
        }
        queryWrapper.lambda().eq(Organization::getIsDeleted, BusinessConstant.DELETE_NO);
        //排序查询
        queryWrapper.orderByAsc("sequence");
        List<Organization> organizationList = list(queryWrapper);
        return organizationList;
    }


    @Override
    public R addOrgRole(Long orgId, List<Long> roleIds, boolean isConduction) {
        Organization organization = getById(orgId);
        if (organization == null) {
            return R.fail(NODE_NO);
        }
        if (roleIds != null && !roleIds.isEmpty()) {
            OrganizationRole orgRole = new OrganizationRole();
            orgRole.setOrganizationId(orgId);
            List<OrganizationRole> orgRoleList = orgRoleService.list(orgRole, null, roleIds);
            //剔除已经存在的
            if (orgRoleList != null && !orgRoleList.isEmpty()) {
                List<Long> oldRoleIds = orgRoleList.stream().map(OrganizationRole::getRoleId).collect(Collectors.toList());
                roleIds.removeAll(oldRoleIds);
            }

            if (roleIds != null && !roleIds.isEmpty()) {
                List<Organization> organizationList = new ArrayList<>();
                if (isConduction) {
                    organizationList = queryAllOfCode(organization.getCode());
                } else {
                    organizationList.add(organization);
                }
                orgRoleService.addOrgRole(organizationList, roleIds, organization.getProjectId());
            }
        }
        return R.success();
    }

    @Override
    public R updOrgRole(Long orgId, List<Long> roleIds, boolean isConduction) {
        //先删除组织下的角色
        removeOrgRole(orgId);
        //添加组织的角色
        addOrgRole(orgId, roleIds, isConduction);
        return R.success();
    }

    @Override
    public R removeOrgRole(Long orgId, List<Long> roleIds, boolean isConduction) {
        Organization organization = getById(orgId);
        if (organization == null) {
            return R.success();
        }
        if (roleIds != null && !roleIds.isEmpty()) {
            List<Organization> organizationList = new ArrayList<>();
            if (isConduction) {
                organizationList = queryAllOfCode(organization.getCode());
            } else {
                organizationList.add(organization);
            }
            orgRoleService.removeOrgRole(organizationList, roleIds, organization.getProjectId());
        }
        return R.success();
    }

    @Override
    public R removeOrgRole(Long orgId) {
        Organization organization = getById(orgId);
        if (organization == null) {
            return R.success();
        }
        //查询节点下的角色关系
        List<OrganizationRole> organizationRoleList = orgRoleService.findOfOrg(Arrays.asList(orgId));
        if (organizationRoleList != null && !organizationRoleList.isEmpty()) {
            //过滤到角色
            List<Long> roleIds = organizationRoleList.stream().map(OrganizationRole::getRoleId).collect(Collectors.toList());
            orgRoleService.removeOrgRole(queryAllOfCode(organization.getCode()), roleIds, organization.getProjectId());
        }
        return R.success();
    }

    @Override
    public R removeOfRole(List<Long> roleIds) {
        return orgRoleService.removeOfRole(roleIds);
    }


    @Override
    public List<Map> loadUserPermission(List<Long> userIdList) {
        if (userIdList == null || userIdList.isEmpty()) {
            return null;
        }
        List<Map> result = new ArrayList<>();
        for (Long userId : userIdList) {
            Map map = new HashMap();
            UserOrganization userOrganization = new UserOrganization();
            userOrganization.setUserId(userId);
            List<UserOrganization> userOrganizationList = userOrganizationService.listOfUserOrganization(userOrganization, null, null);
            if (userOrganizationList != null && !userOrganizationList.isEmpty()) {
                //将角色加载进去
                List<Long> orgIds = userOrganizationList.stream().map(UserOrganization::getOrganizationId).collect(Collectors.toList());
                List<RoleVo> roleVoList = loadRole(orgIds);
                List<String> permissionList = loadMenuPermission(roleVoList);
                //添加到缓存
                CacheKey cacheKey = new PermissionCacheKeyBuilder().key(userId);
                cacheOps.set(cacheKey, permissionList);
                map.put("userId", userId);
                map.put("permissionList", permissionList);
                result.add(map);
                System.out.println(JSON.toJSONString(map));
            }
        }
        return result;
    }

    @Override
    public List<Map> loadUserPermissionOfOrg(List<Long> orgIdList) {
        List<UserOrganization> userOrganizationList = userOrganizationService.listOfUserOrganization(null, null, orgIdList);
        if (userOrganizationList != null && !userOrganizationList.isEmpty()) {
            List<Long> userIdList = userOrganizationList.stream().map(UserOrganization::getUserId).collect(Collectors.toList());
            return loadUserPermission(userIdList);
        }
        return null;
    }

    @Override
    public List<Map> loadUserPermissionOfRole(List<Long> roleIdList) {
        List<OrganizationRole> organizationRoleList = orgRoleService.findOfRole(roleIdList);
        if (organizationRoleList != null && !organizationRoleList.isEmpty()) {
            List<Long> orgIdList = organizationRoleList.stream().map(OrganizationRole::getOrganizationId).collect(Collectors.toList());
            return loadUserPermissionOfOrg(orgIdList);
        }
        return null;
    }

    @Override
    public Boolean isPermission(Long userId, String[] permission) {
        CacheKey cacheKey = new PermissionCacheKeyBuilder().key(userId);
        List<String> permissionList = cacheOps.get(cacheKey);
        if (permissionList == null || permissionList.isEmpty()) {
            //重新加载信息
            List<Map> maps = loadUserPermission(Arrays.asList(userId));
            if (maps != null && !maps.isEmpty()) {
                for (Map map : maps) {
                    if (((Long) map.get("userId")) == userId) {
                        permissionList = (List<String>) map.get("permissionList");
                    }
                }
            }
        }
        //判断是否有权限
        if (permissionList != null && !permissionList.isEmpty()) {
            for (String s : permission) {
                if (permissionList.contains(s)) {
                    return true;
                }
            }
        }
        return false;
    }


    public OrganizationVo doToVo(Organization organization) {
        OrganizationVo organizationVo = new OrganizationVo();
        BeanUtils.copyProperties(organization, organizationVo);
        organizationVo.setId(organization.getId());
        return organizationVo;
    }

    public List<OrganizationVo> doToVos(List<Organization> organizationList) {
        if (organizationList == null || organizationList.isEmpty()) {
            return null;
        }
        List<OrganizationVo> result = new ArrayList<>();
        for (Organization organization : organizationList) {
            result.add(doToVo(organization));
        }
        return result;
    }
}
